home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 7 / Apprentice-Release7.iso / Source Code / PowerPlant / CPrefFile / CPrefFile.cp next >
Encoding:
Text File  |  1997-01-22  |  11.0 KB  |  444 lines  |  [TEXT/CWIE]

  1. // ===========================================================================
  2. // CPrefFile.cp           ©1996 Sunbay Development Group. All rights reserved.
  3. // ===========================================================================
  4. // 
  5.  
  6. #ifdef PowerPlant_PCH
  7. #include PowerPlant_PCH
  8. #endif
  9.  
  10. #ifndef __ALIASES__
  11. #include <Aliases.h>
  12. #endif
  13.  
  14. #ifndef __FILES__
  15. #include <Files.h>
  16. #endif
  17.  
  18. #ifndef __FOLDERS__
  19. #include <Folders.h>
  20. #endif
  21.  
  22. #ifndef __RESOURCESES__
  23. #include <Resources.h>
  24. #endif
  25.  
  26. #ifndef __ERRORS__
  27. #include <Errors.h>
  28. #endif
  29.  
  30. #include <String_Utils.h>
  31.  
  32. #include "CPrefFile.h"
  33.  
  34. const Int16 refNum_Undefined = -1;
  35.  
  36. // ===========================================================================
  37. #pragma mark •--- Constructors
  38. // ===========================================================================
  39.  
  40. // ---------------------------------------------------------------------------
  41. // Constructors
  42. // ---------------------------------------------------------------------------
  43.  
  44. CPrefFile::CPrefFile(void) : LFile() {
  45. }
  46.  
  47. CPrefFile::CPrefFile(ConstStr255Param inFileName, Boolean inCreateFolder) : LFile() {
  48.     Int16    vref;
  49.     Int32    dirID;
  50.     OSErr    error;
  51.  
  52.     error = ::FindFolder(    kOnSystemDisk,
  53.                             kPreferencesFolderType,
  54.                             inCreateFolder,
  55.                             &vref,
  56.                             &dirID);
  57.     if(error == noErr)
  58.         error = ::FSMakeFSSpec(vref, dirID, inFileName, &mMacFileSpec);
  59.     else
  60.         CopyPStr(inFileName, mMacFileSpec.name, sizeof (Str63));
  61. }
  62.  
  63. // ---------------------------------------------------------------------------
  64. // Set new file name
  65. // ---------------------------------------------------------------------------
  66.  
  67. OSErr CPrefFile::SetName(ConstStr255Param inFileName, Boolean inCreateFolder) {
  68.     Int16    vref;
  69.     Int32    dirID;
  70.     OSErr    error;
  71.  
  72.     //        Has file not been closed?
  73.     if(mDataForkRefNum != refNum_Undefined || mResourceForkRefNum != refNum_Undefined)
  74.         return opWrErr;
  75.     //        Default initialisation for file specification
  76.     mMacFileSpec.vRefNum    = 0;
  77.     mMacFileSpec.parID        = 0;
  78.     mMacFileSpec.name[0]    = 0;
  79.     //        Find preferences folder
  80.     error = ::FindFolder(    kOnSystemDisk,
  81.                             kPreferencesFolderType,
  82.                             inCreateFolder,
  83.                             &vref,
  84.                             &dirID);
  85.     if(error != noErr) return error;
  86.     //        Set new name
  87.     error = ::FSMakeFSSpec(vref, dirID, inFileName, &mMacFileSpec);
  88.     return error;
  89. }
  90.  
  91. // ===========================================================================
  92. #pragma mark •--- Create group
  93. // ===========================================================================
  94.  
  95. // ---------------------------------------------------------------------------
  96. // Create new file
  97. // ---------------------------------------------------------------------------
  98.  
  99. OSErr CPrefFile::CreateFile(
  100.     OSType        inCreator,
  101.     OSType        inFileType,
  102.     ScriptCode    inScriptCode)
  103. {
  104.     FInfo    finfo;
  105.     OSErr    error;
  106.  
  107.     if(mDataForkRefNum != refNum_Undefined || mResourceForkRefNum != refNum_Undefined) {
  108.         //        File has not been closed
  109.         return opWrErr;
  110.     }
  111.     if((error = ::FSpCreate(&mMacFileSpec, inCreator, inFileType, inScriptCode)) == noErr) {
  112.         ::FSpCreateResFile(&mMacFileSpec, inCreator, inFileType, inScriptCode);
  113.         error = ::ResError();
  114.     }
  115.     return error;
  116. }
  117.  
  118. // ---------------------------------------------------------------------------
  119. // Create data fork
  120. // ---------------------------------------------------------------------------
  121.  
  122. OSErr CPrefFile::CreateDatFork(
  123.     OSType        inCreator,
  124.     OSType        inFileType,
  125.     ScriptCode    inScriptCode)
  126. {
  127.     short    refn;
  128.     OSErr    error = noErr;
  129.  
  130.     if(mDataForkRefNum != refNum_Undefined)
  131.         return noErr;
  132.     //        Does data fork exist?
  133.     if((error = ::FSpOpenDF(&mMacFileSpec, fsRdPerm, &refn)) == noErr) {
  134.         ::FSClose(refn);
  135.         return noErr;
  136.     }
  137.     //        Data fork does not exist
  138.     error = ::FSpCreate(&mMacFileSpec, inCreator, inFileType, inScriptCode);
  139.     return error;
  140. }
  141.  
  142. // ---------------------------------------------------------------------------
  143. // Create resource fork
  144. // ---------------------------------------------------------------------------
  145.  
  146. OSErr CPrefFile::CreateResFork(
  147.     OSType        inCreator,
  148.     OSType        inFileType,
  149.     ScriptCode    inScriptCode)
  150. {
  151.     short    refn;
  152.     OSErr    error = noErr;
  153.  
  154.     if(mResourceForkRefNum != refNum_Undefined)
  155.         return noErr;
  156.     //        Does resource fork exist?
  157.     refn = ::FSpOpenResFile(&mMacFileSpec, fsRdPerm);
  158.     if(::ResError() == noErr) {
  159.         ::CloseResFile(refn);
  160.         return noErr;
  161.     }
  162.     //        Resource fork does not exist
  163.     ::FSpCreateResFile(&mMacFileSpec, inCreator, inFileType, inScriptCode);
  164.     error = ::ResError();
  165.     return error;
  166. }
  167.  
  168. // ===========================================================================
  169. #pragma mark •--- Open group
  170. // ===========================================================================
  171.  
  172. // ---------------------------------------------------------------------------
  173. // Open resource fork
  174. // ---------------------------------------------------------------------------
  175.  
  176. OSErr CPrefFile::OpenResFork(Int16 inPrivileges) {
  177.     OSErr    error = noErr;
  178.  
  179.     mResourceForkRefNum = ::FSpOpenResFile(&mMacFileSpec, inPrivileges);
  180.     if(mResourceForkRefNum == refNum_Undefined) {
  181.         error = ::ResError();
  182.         mResourceForkRefNum = refNum_Undefined;
  183.     }
  184.     return error;
  185. }
  186.  
  187. // ---------------------------------------------------------------------------
  188. // Open data fork
  189. // ---------------------------------------------------------------------------
  190.  
  191. OSErr CPrefFile::OpenDatFork(Int16 inPrivileges) {
  192.     OSErr    error = noErr;
  193.  
  194.     error = ::FSpOpenDF(&mMacFileSpec, inPrivileges, &mDataForkRefNum);
  195.     if(error != noErr)
  196.         mDataForkRefNum = refNum_Undefined;
  197.     return error;
  198. }
  199.  
  200. // ===========================================================================
  201. #pragma mark •--- Close group
  202. // ===========================================================================
  203.  
  204. // ---------------------------------------------------------------------------
  205. // Close data fork
  206. // ---------------------------------------------------------------------------
  207.  
  208. OSErr CPrefFile::CloseDatFork(void) {
  209.     OSErr    error = noErr;
  210.  
  211.     if(mDataForkRefNum != refNum_Undefined) {
  212.         //        Close data fork
  213.         error = ::FSClose(mDataForkRefNum);
  214.         mDataForkRefNum = refNum_Undefined;
  215.         if(error != noErr) return error;
  216.         ::FlushVol(nil, mMacFileSpec.vRefNum);
  217.     }
  218.     return error;
  219. }
  220.  
  221. // ---------------------------------------------------------------------------
  222. // Closer resource fork
  223. // ---------------------------------------------------------------------------
  224.  
  225. OSErr CPrefFile::CloseResFork(void) {
  226.     OSErr    error = noErr;
  227.  
  228.     if(mResourceForkRefNum != refNum_Undefined) {
  229.         //        Close resource fork
  230.         ::CloseResFile(mResourceForkRefNum);
  231.         error = ::ResError();
  232.         mResourceForkRefNum = refNum_Undefined;
  233.         if(error != noErr) return error;
  234.         ::FlushVol(nil, mMacFileSpec.vRefNum);
  235.     }
  236.     return error;
  237. }
  238.  
  239. // ===========================================================================
  240. #pragma mark •--- Resource support group
  241. // ===========================================================================
  242.  
  243. // ---------------------------------------------------------------------------
  244. // Create new resource
  245. // ---------------------------------------------------------------------------
  246.  
  247. OSErr CPrefFile::NewResource(
  248.     void *                resdata,
  249.     long                ressize,
  250.     ResType                restype,
  251.     short                resid,
  252.     ConstStr255Param    resname)
  253. {
  254.  
  255.     enum modet {
  256.         mdStart,
  257.         mdResFExist,
  258.         mdResRdError,
  259.         mdMemAlloc,
  260.         mdSuccess
  261.     };
  262.  
  263.     short    refn;
  264.     Handle    resH;
  265.     modet    mode;
  266.     OSErr    error;
  267.  
  268.     if(mResourceForkRefNum == refNum_Undefined) return resFNotFound;
  269.     for(;;) {
  270.         mode = mdStart;
  271.         refn = ::CurResFile();
  272.         if(refn != mResourceForkRefNum) {
  273.             ::UseResFile(mResourceForkRefNum);
  274.             if((error = ::ResError()) != noErr) break;
  275.         }
  276.         mode = mdResFExist;
  277.         //        Is target resource exist
  278.         if((resH = ::Get1Resource(restype, resid)) != nil) break;
  279.         mode = mdResRdError;
  280.         error = ::ResError();
  281.         if(!(error != resNotFound || error != noErr)) break;
  282.         //        Prepare handle
  283.         if((error = ::PtrToHand(resdata, &resH, ressize)) != noErr) break;
  284.         mode = mdMemAlloc;
  285.         ::HNoPurge(resH);
  286.         ::AddResource(resH, restype, resid, resname);
  287.         if((error = ::ResError()) != noErr) break;
  288.         ::WriteResource(resH);
  289.         ::HPurge(resH);
  290.         if((error = ::ResError()) != noErr) break;
  291.         ::ReleaseResource(resH);
  292.         mode = mdSuccess;
  293.         break;
  294.     }
  295.     switch(mode) {
  296.         case mdSuccess:
  297.             error = noErr;
  298.             break;
  299.         case mdResFExist:
  300.             ::ReleaseResource(resH);
  301.             error = addResFailed;
  302.             break;
  303.         case mdMemAlloc:
  304.             ::DisposeHandle(resH);
  305.         case mdStart:
  306.         case mdResRdError:
  307.         default:
  308.             break;
  309.     }
  310.     if(refn != mResourceForkRefNum) ::UseResFile(refn);
  311.     return error;
  312. }
  313.  
  314. // ---------------------------------------------------------------------------
  315. // Put into resource
  316. // ---------------------------------------------------------------------------
  317.  
  318. OSErr CPrefFile::PutResource(
  319.     void *                resdata,
  320.     long                ressize,
  321.     ResType                restype,
  322.     short                resid,
  323.     ConstStr255Param    resname)
  324. {
  325.  
  326.     enum modet {
  327.         mdStart,
  328.         mdResExist,
  329.         mdResRdOk,
  330.         mdMemAlloc,
  331.         mdSuccess
  332.     };
  333.  
  334.     short    refn;
  335.     Handle    resH;
  336.     modet    mode;
  337.     OSErr    error;
  338.  
  339.     if(mResourceForkRefNum == refNum_Undefined) return resFNotFound;
  340.     for(;;) {
  341.         mode = mdStart;
  342.         refn = ::CurResFile();
  343.         if(refn != mResourceForkRefNum) {
  344.             ::UseResFile(mResourceForkRefNum);
  345.             if((error = ::ResError()) != noErr) break;
  346.         }
  347.         mode = mdResExist;
  348.         //        Is target resource exist
  349.         if((resH = ::Get1Resource(restype, resid)) == nil) break;
  350.         mode = mdResRdOk;
  351.         //        Prepare handle
  352.         if((error = ::PtrToXHand(resdata, resH, ressize)) != noErr) break;
  353.         mode = mdMemAlloc;
  354.         ::HNoPurge(resH);
  355.         ::ChangedResource(resH);
  356.         if((error = ::ResError()) != noErr) break;
  357.         ::WriteResource(resH);
  358.         if((error = ::ResError()) != noErr) break;
  359.         ::HPurge(resH);
  360.         ::ReleaseResource(resH);
  361.         error = ::ResError();
  362.         mode = mdSuccess;
  363.         break;
  364.     }
  365.     switch(mode) {
  366.         case mdMemAlloc:
  367.             ::HPurge(resH);
  368.         case mdResRdOk:
  369.             ::ReleaseResource(resH);
  370.             break;
  371.         case mdResExist:
  372.             error = resNotFound;
  373.             break;
  374.         case mdStart:
  375.         case mdSuccess:
  376.         default:
  377.             break;
  378.     }
  379.     if(refn != mResourceForkRefNum) ::UseResFile(refn);
  380.     return error;
  381. }
  382.  
  383. // ---------------------------------------------------------------------------
  384. // Get from resource
  385. // ---------------------------------------------------------------------------
  386.  
  387. OSErr CPrefFile::GetResource(
  388.     void *                resdata,
  389.     long                ressize,
  390.     ResType                restype,
  391.     short                resid,
  392.     ConstStr255Param    resname)
  393. {
  394.  
  395.     enum modet {
  396.         mdStart,
  397.         mdResExist,
  398.         mdResRdOk,
  399.         mdSuccess
  400.     };
  401.  
  402.     short    refn;
  403.     Handle    resH;
  404.     modet    mode;
  405.     OSErr    error;
  406.  
  407.     if(mResourceForkRefNum == refNum_Undefined) return resFNotFound;
  408.     if(resdata == nil) return notEnoughMemoryErr;
  409.     for(;;) {
  410.         mode = mdStart;
  411.         refn = ::CurResFile();
  412.         if(refn != mResourceForkRefNum) {
  413.             ::UseResFile(mResourceForkRefNum);
  414.             if((error = ::ResError()) != noErr) break;
  415.         }
  416.         mode = mdResExist;
  417.         //        Is target resource exist
  418.         if((resH = ::Get1Resource(restype, resid)) == nil) break;
  419.         mode = mdResRdOk;
  420.         //        Copy read resource to the pointer
  421.         ::HLock(resH);
  422.         ::BlockMove(*resH, resdata, ressize);
  423.         ::HUnlock(resH);
  424.         ::ReleaseResource(resH);
  425.         error = ::ResError();
  426.         mode = mdSuccess;
  427.         break;
  428.     }
  429.     switch(mode) {
  430.         case mdResRdOk:
  431.             ::ReleaseResource(resH);
  432.             break;
  433.         case mdResExist:
  434.             error = resNotFound;
  435.             break;
  436.         case mdStart:
  437.         case mdSuccess:
  438.         default:
  439.             break;
  440.     }
  441.     if(refn != mResourceForkRefNum) ::UseResFile(refn);
  442.     return error;
  443. }
  444.